﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
using Newtonsoft.Json.Linq;

namespace Atmk.WaterMeter.MIS.Commons.Utils
{
    public class PropertyHelper
    {
        /// <summary>
        /// 根据属性，获取属性名称字符串
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="expr"></param>
        /// <returns></returns>
        public static string GetPropertyName<T>(Expression<Func<T, object>> expr)
        {
            var rtn = "";
            switch (expr.Body)
            {
                case UnaryExpression expression:
                    rtn = ((MemberExpression) expression.Operand).Member.Name;
                    break;
                case MemberExpression _:
                    rtn = ((MemberExpression) expr.Body).Member.Name;
                    break;
                case ParameterExpression _:
                    rtn = ((ParameterExpression) expr.Body).Type.Name;
                    break;
            }
            return rtn;
        }
        /// <summary>
        /// 返回没有值的属性名称集合
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="t"></param>
        /// <returns></returns>
        public static List<string> GetNoValuePropertyName<T>(T t)
        {
            var result = t.GetType().GetProperties()
                    .Where(p=>p.GetValue(t) == null)
                .Select(p => p.Name).ToList();
            return result;
        }
        /// <summary>
        /// 将对象中属性名和值类型与JObject里key与相同的属性进行赋值
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="t"></param>
        /// <param name="j"></param>
        /// <returns></returns>
        public static T SetJobjectePropertyName<T>(T t, JObject j)
        {
            foreach (var propertyInfo in t.GetType().GetProperties())
            {
                var pName = propertyInfo.Name;
                if (!j.ContainsKey(pName)) continue;
                var jvalue = j[pName].ToString();
                if (propertyInfo.PropertyType==typeof(string))
                    propertyInfo.SetValue(t, jvalue,null);
                if (propertyInfo.PropertyType == typeof(int))
                {
                    int.TryParse(jvalue, out var pValue);
                    propertyInfo.SetValue(t, pValue,null);
                }
            }
            return t;
        }
    }
}